package com.inspur.edp.bef.bemanager.compcodebutton;

import com.inspur.edp.bef.bemanager.codegenerator.JavaCmpCodeGeneratorFactory;
import com.inspur.edp.bef.bemanager.codegenerator.actions.JavaBaseCommonCompCodeGen;
import com.inspur.edp.bef.bemanager.util.CheckInfoUtil;
import com.inspur.edp.bef.bizentity.GspBizEntityObject;
import com.inspur.edp.bef.bizentity.GspBusinessEntity;
import com.inspur.edp.bef.bizentity.exceptions.BusinessEntityErrorCodeEnum;
import com.inspur.edp.bef.bizentity.exceptions.BusinessEntityException;
import com.inspur.edp.bef.bizentity.operation.BizOperation;
import com.inspur.edp.bef.bizentity.operation.TccAction;
import com.inspur.edp.bef.bizentity.operation.internalmgraction.TccSettingElement;
import com.inspur.edp.cef.designtime.api.operation.CommonDetermination;
import com.inspur.edp.cef.designtime.api.operation.CommonOperation;
import com.inspur.edp.cef.variable.dtgenerator.vardtmGenerate.javageneratecmpcode.JavaCommonDeterminationGenerator;
import com.inspur.edp.lcm.metadata.api.service.FileService;
import com.inspur.edp.lcm.metadata.api.service.MetadataProjectService;
import io.iec.edp.caf.commons.utils.SpringBeanUtils;

import java.io.IOException;
import java.util.ArrayList;

public class CompPathButton {

    private static final String javaCodeFileExtension = ".java";
    private static final String javaPathInfo = "java\\code\\comp\\src\\main\\java\\com";
    private final FileService fsService = SpringBeanUtils.getBean(FileService.class);

    public String getCompPath(GspBusinessEntity be, String type, String relativePath, ArrayList<String> actionList, String compAssemblyName) {

        //GetJavaCompModulePath
        String generatingAssembly = be.getDotnetGeneratingAssembly().replace(".", "\\");
        String compositePath = "";
        BizOperation op = initAction(type, be, actionList);
        GspBizEntityObject belongNode = initBelongNode(type, be, actionList);
        String filePath = "";

        if ("BizActions".equals(type)) {
            compositePath = CheckInfoUtil.getCombinePath(javaPathInfo, generatingAssembly.toLowerCase(), type.toLowerCase());
        }else if("VarDeterminations".equals(type)){
            String temPath = CheckInfoUtil.getCombinePath(be.getCode().toLowerCase(), type.toLowerCase());
            compositePath = CheckInfoUtil.getCombinePath(javaPathInfo, generatingAssembly.toLowerCase(), temPath);
        } else {
            String temPath = CheckInfoUtil.getCombinePath(belongNode.getCode().toLowerCase(), type.toLowerCase());
            compositePath = CheckInfoUtil.getCombinePath(javaPathInfo, generatingAssembly.toLowerCase(), temPath);
        }

        if(!"VarDeterminations".equals(type)) {
            JavaBaseCommonCompCodeGen codeGen = (belongNode == null || belongNode.getIsRootNode()) ?
                    JavaCmpCodeGeneratorFactory.JavaGetGenerator(be, op, compAssemblyName, relativePath) :
                    JavaCmpCodeGeneratorFactory.JavaGetChildNodeGenerator(be, belongNode.getCode(), op, compAssemblyName, relativePath);
            filePath = CheckInfoUtil.getCombinePath(compositePath, codeGen.GetCompName() + javaCodeFileExtension);

        }else {
            CommonOperation dtm = initDtm(be,actionList);
            JavaCommonDeterminationGenerator gen = new JavaCommonDeterminationGenerator(be, dtm, compAssemblyName, relativePath);
            filePath = CheckInfoUtil.getCombinePath(compositePath, gen.getCompName() + javaCodeFileExtension);
        }
        return filePath;
    }

    private BizOperation initAction(String type, GspBusinessEntity be, ArrayList<String> actionList) {
        java.util.ArrayList<GspBizEntityObject> nodes = be.getAllNodes();
        switch (type) {
            case "BizActions":
                for (BizOperation action : be.getCustomMgrActions()) {
                    if (actionList.contains(action.getCode()))
                        return action;
                }
                break;
            case "EntityActions":
                for (GspBizEntityObject node : nodes) {
                    for (BizOperation action : node.getCustomBEActions()) {
                        if(actionList.contains(action.getCode())){
                            return action;
                        }
                    }
                }
                break;
            case "TccActions":
                for (GspBizEntityObject node : nodes) {
                    for(TccSettingElement ele: node.getTccSettings()) {
                        TccAction action = ele.getTccAction();
                        if(actionList.contains(action.getCode())) {
                            return action;
                        }
                    }
                }
                break;
            case "Determinations":
                for (GspBizEntityObject node : be.getAllNodes()) {
                    for (BizOperation action : node.getDeterminations()) {
                        if(actionList.contains(action.getCode())) {
                            return action;
                        }
                    }
                }
                break;
            case "Validations":
                for (GspBizEntityObject node : be.getAllNodes()) {
                    for (BizOperation action : node.getValidations()) {
                        if(actionList.contains(action.getCode())) {
                            return action;
                        }
                    }
                }
                break;
            case "VarDeterminations":
                return null;
            default:
                throw BusinessEntityException.createException(BusinessEntityErrorCodeEnum.GSP_BEMODEL_ENUM_NOTSUPPORT_0006, type);
        }
        return null;
    }

    private GspBizEntityObject initBelongNode(String type, GspBusinessEntity be, ArrayList<String> actionList) {
        java.util.ArrayList<GspBizEntityObject> nodes = be.getAllNodes();
        switch (type) {
            case "BizActions":
            case "VarDeterminations":
                return null;
            case "EntityActions":
                for(GspBizEntityObject node : nodes){
                    for (BizOperation action : node.getCustomBEActions()) {
                        if(actionList.contains(action.getCode())){
                            return node;
                        }
                    }
                }
            case "TccActions":
                for (GspBizEntityObject node : nodes) {
                    for(TccSettingElement ele: node.getTccSettings()) {
                        TccAction action = ele.getTccAction();
                        if(actionList.contains(action.getCode())) {
                            return node;
                        }
                    }
                }
                break;
            case "Determinations":
                for (GspBizEntityObject node : be.getAllNodes()) {
                    for (BizOperation action : node.getDeterminations()) {
                        if(actionList.contains(action.getCode())) {
                            return node;
                        }
                    }
                }
                break;
            case "Validations":
                for (GspBizEntityObject node : be.getAllNodes()) {
                    for (BizOperation action : node.getValidations()) {
                        if(actionList.contains(action.getCode())) {
                            return node;
                        }
                    }
                }
                break;
            default:
                throw BusinessEntityException.createException(BusinessEntityErrorCodeEnum.GSP_BEMODEL_ENUM_NOTSUPPORT_0006, type);
        }
        return null;
    }

    public CommonOperation initDtm(GspBusinessEntity be,ArrayList<String> actionList){
        CommonOperation dt = new CommonDetermination();
        for (CommonDetermination dtm : be.getVariables().getDtmAfterModify()) {
            if (dtm.getIsRef() || !dtm.getIsGenerateComponent() || !actionList.contains(dtm.getCode())) {
                continue;
            }
            dt = dtm;
        }
        return dt;
    }

    public String getFilePath(GspBusinessEntity be, String type, ArrayList<String> actionList, String relativePath){

        String generatingAssembly = be.getDotnetGeneratingAssembly().replace(".", "\\");
        String compositePath = "";
        GspBizEntityObject belongNode = initBelongNode(type, be, actionList);
        String filePath = "";

        MetadataProjectService service = SpringBeanUtils.getBean(MetadataProjectService.class);
        String compModulePath = CheckInfoUtil.getCombinePath(service.getJavaCompProjectPath(relativePath),"com");

        if ("BizActions".equals(type)) {
            compositePath = CheckInfoUtil.getCombinePath(compModulePath, generatingAssembly.toLowerCase(), type.toLowerCase());
        }else if("VarDeterminations".equals(type)){
            String temPath = CheckInfoUtil.getCombinePath(be.getCode().toLowerCase(), type.toLowerCase());
            compositePath = CheckInfoUtil.getCombinePath(compModulePath, generatingAssembly.toLowerCase(), temPath);
        } else {
            String temPath = CheckInfoUtil.getCombinePath(belongNode.getCode().toLowerCase(), type.toLowerCase());
            compositePath = CheckInfoUtil.getCombinePath(compModulePath, generatingAssembly.toLowerCase(), temPath);
        }
        if("BizActions".equals(type)||"VarDeterminations".equals(type)){
            filePath = CheckInfoUtil.getCombinePath(compositePath, compName(type, null, actionList.get(0), be.getCode()));
        }else {
            filePath = CheckInfoUtil.getCombinePath(compositePath, compName(type, belongNode.getCode().toLowerCase(), actionList.get(0), null));
        }
        return filePath;
    }

    private String compName(String type,String objCode,String actionCode,String beCode){
        switch (type){
            case "BizActions":
                return  beCode+actionCode+"MgrAction.java";
            case "EntityActions":
                return  objCode+actionCode+"Action.java";
            case "TccActions":
                return  objCode+actionCode+"TccAction.java";
            case "Determinations":
                return  objCode+actionCode+"Determination.java";
            case "Validations":
                return  objCode+actionCode+"Validation.java";
            case "VarDeterminations":
                return  beCode+"Variable"+actionCode+"VODtm.java";
            default:
                throw BusinessEntityException.createException(BusinessEntityErrorCodeEnum.GSP_BEMODEL_ENUM_NOTSUPPORT_0006, type);
        }
    }

    public void JavaReplace(String filePath) {
        String oldValue = "import com.inspur.Gsp.bef.entity.changeset;";
        String newValue = "import inspur.Gsp.cef.entity.changeset;";
        String content = null;
        try {
            content = fsService.fileRead(filePath);
        } catch (IOException e) {
            throw BusinessEntityException.createException(BusinessEntityErrorCodeEnum.GSP_BEMODEL_BUSINESS_ENTITY_0084, e, filePath);
        }
        if (!content.contains(oldValue)) {
            return;
        }
        content = content.replace(oldValue, newValue);
        fsService.fileUpdate(filePath, content);
    }

}
